package com.rs.service;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

import com.rs.dao.TouristInfoDao;
import com.rs.entities.Hotel;
import com.rs.entities.HotelPicture;
import com.rs.entities.Nearby;
import com.rs.entities.Picture;
import com.rs.entities.Restaurant;
import com.rs.entities.RestaurantPicture;
import com.rs.entities.Scenic;
import com.rs.entities.ScenicPicture;
import com.rs.entities.ScenicRequest;

import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import net.sf.json.JsonConfig;
import net.sf.json.util.CycleDetectionStrategy;

public class TouristInfoService {
	private TouristInfoDao touristInfoDao;

	public void setTouristInfoDao(TouristInfoDao touristInfoDao) {
		this.touristInfoDao = touristInfoDao;
	}

	public JSONObject getScenicList(ScenicRequest request) {
		JSONObject jsonObject = new JSONObject();
		List<Scenic> scenicList = touristInfoDao.getScenicList(request);
		JSONArray jsonArray = new JSONArray();
		JsonConfig jsonConfig = new JsonConfig();
		jsonConfig.setIgnoreDefaultExcludes(false);
		jsonConfig.setExcludes(new String[] { "pictures" });
		jsonConfig.setCycleDetectionStrategy(CycleDetectionStrategy.LENIENT);
		for (Scenic scenic : scenicList) {
			List<Picture> pictures = new ArrayList<>();
			for (ScenicPicture r : scenic.getPictures()) {
				Picture p = new Picture(r);
				pictures.add(p);
			}
			sort(pictures);
			JSONObject resJson = null;
			try {
				resJson = JSONObject.fromObject(scenic, jsonConfig);
				resJson.put("pictures", JSONArray.fromObject(pictures));
			} catch (Exception e) {
				e.printStackTrace();
			}
			jsonArray.add(resJson);
		}
		jsonObject.put("scenicList", jsonArray);
		return jsonObject;
	}

	public JSONObject getHotelList(Nearby nearby) {
		List<Hotel> hotelList = touristInfoDao.getHotelList(nearby);
		JSONObject jsonObject = new JSONObject();
		JSONArray jsonArray = new JSONArray();
		JsonConfig jsonConfig = new JsonConfig();
		jsonConfig.setIgnoreDefaultExcludes(false);
		jsonConfig.setExcludes(new String[] { "pictures" });
		jsonConfig.setCycleDetectionStrategy(CycleDetectionStrategy.LENIENT);
		for (Hotel hotel : hotelList) {
			List<Picture> pictures = new ArrayList<>();
			for (HotelPicture r : hotel.getPictures()) {
				Picture p = new Picture(r);
				pictures.add(p);
			}
			sort(pictures);
			JSONObject resJson = null;
			try {
				resJson = JSONObject.fromObject(hotel, jsonConfig);
				resJson.put("pictures", JSONArray.fromObject(pictures));
			} catch (Exception e) {
				e.printStackTrace();
			}
			jsonArray.add(resJson);
		}
		jsonObject.put("hotelList", jsonArray);
		return jsonObject;
	}

	public JSONObject getRestaurantList(Nearby nearby) {
		List<Restaurant> restaurantList = touristInfoDao.getRestaurantList(nearby);
		JSONObject jsonObject = new JSONObject();
		JSONArray jsonArray = new JSONArray();
		JsonConfig jsonConfig = new JsonConfig();
		jsonConfig.setIgnoreDefaultExcludes(false);
		jsonConfig.setExcludes(new String[] { "pictures" });
		jsonConfig.setCycleDetectionStrategy(CycleDetectionStrategy.LENIENT);
		for (Restaurant restaurant : restaurantList) {
			List<Picture> pictures = new ArrayList<>();
			for (RestaurantPicture r : restaurant.getPictures()) {
				Picture p = new Picture(r);
				pictures.add(p);
			}
			sort(pictures);
			/*
			 * for (int i = 0; i < pictures.size(); i++) {
			 * System.out.println(pictures.get(i).getPicPath()); }
			 */
			JSONObject resJson = null;
			try {
				resJson = JSONObject.fromObject(restaurant, jsonConfig);
				resJson.put("pictures", JSONArray.fromObject(pictures));
			} catch (Exception e) {
				e.printStackTrace();
			}
			jsonArray.add(resJson);
		}
		jsonObject.put("restaurantList", jsonArray);
		return jsonObject;
	}

	private void sort(List<Picture> pictures) {
		Collections.sort(pictures, new Comparator<Picture>() {
			@Override
			public int compare(Picture lhs, Picture rhs) {
				return lhs.getPicPath().compareTo(rhs.getPicPath());
			}
		});

	}

	public void insert(String fileName) {
		touristInfoDao.insert(fileName);
	}
}
